#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define printf(fmt, ...) NULL
/**
 * Return an array of size *returnSize.
 * Note: The returned array must be malloced, assume caller calls free().
 */
char** removeComments(char** source, int sourceSize, int* returnSize) {
    char **ret = NULL;
    int i = 0;
    int block = 0;
    int block_continue = 0;
    char *tar = NULL;
    *returnSize = 0;
    for(; i < sourceSize; i++) {
        char *sour = source[i];
        Head: {
            if(block) {
                char *p = strstr(sour, "*/");
                if(p) {
                    printf("find */ %d %s!\n", i, sour);
                    block = 0;
                    p += 2;
                    if(*p) {
                        sour = p;
                        goto Head;
                    }
                    tar = NULL;
                    continue;
                } else {
                    continue;
                }
            } else {
                char *p1 = strstr(sour, "/*");
                char *p2 = strstr(sour, "//");
                if(p1 && p2) {
                    if(p1 > p2) {
                        p1 = NULL;
                    } else {
                        p2 = NULL;
                    }
                }
                if(p1) {
                    printf("find /* %d %s!\n", i, sour);
                    block = 1;
                    if(p1 != sour) {
                        if(tar) {
                            *p1 = '\0';
                            strcat(tar, sour);
                        } else {
                            ++*returnSize;
                            ret = realloc(ret, *returnSize * sizeof(char *));
                            ret[*returnSize - 1] = calloc(1, 80);
                            tar = ret[*returnSize - 1];
                            memcpy(tar, sour, p1 - sour);
                        }
                    }
                    p1 += 2;
                    if(*p1) {
                        sour = p1;
                        printf("/* and goto head !\n");
                        goto Head;
                    } else {
                        continue;
                    }
                } else if(p2) {
                    printf("find // %d %s!\n", i, sour);
                    if(p2 != sour) {
                        if(tar) {
                            printf("!!! %s %s, %s\n", tar, sour, p2);
                            *p2 = '\0';
                            strcat(tar, sour);
                        } else {
                            printf("??\n");
                            ++*returnSize;
                            ret = realloc(ret, *returnSize * sizeof(char *));
                            ret[*returnSize - 1] = calloc(1, 80);
                            tar = ret[*returnSize - 1];
                            memcpy(tar, sour, p2 - sour);
                        }
                    }
                    tar = NULL;
                    continue;
                } else {
                    if(tar) {
                        strcat(tar, sour);
                    } else {
                        ++*returnSize;
                        ret = realloc(ret, *returnSize * sizeof(char *));
                        ret[*returnSize - 1] = calloc(1, 80);
                        strcat(ret[*returnSize - 1], sour);
                    }
                    tar = NULL;
                    continue;
                }
            }
        }
    }
    return ret;
}
// char *sources[] = {"/*Test program */", "int main()", "{ ", "  // variable declaration ", "int a, b, c;", "/* This is a test", "   multiline  ", "   comment for ", "   testing */", "a = b + c;", "}"};
// int len = 11;

char *sources[] = {"a/*/b//\*c","blank","d/*/e*//f"};
int len = 3;
int main(int argc, char *argv[])
{
    int l;
    char **ret = removeComments(sources, len, &l);
    int i = 0;
    printf("get %d:\n", l);
    for(; i < l; i++) {
        printf("%s\n", ret[i]);
    }
    return 0;
}